using System;
using System.IO;
using System.Collections.Generic;
using System.Text;
using usm.SolDev.Common;
namespace usm.SolDev.DataBase.DataObjects.Experiment
{
    /// <summary>
    ///     This is DRG and VSP parser 
    /// </summary>
    public class Parser : DataObject
    {
        #region Private fields
        private List<Experiment> experiments = new List<Experiment>();
        private List<Entity> entities = new List<Entity>();
        #endregion

        #region Constructors
        /// <summary>
        ///     Default constructor
        /// </summary>
        public Parser() { }

        /// <summary>
        ///     Initialization constructor. Load DRG data 
        /// into memory from a DRG file.
        /// </summary>
        /// <param name="fileName"></param>
        /// <throws> Throws an IO Exception</throws>
        public Parser(string drgFileName, string vspFileName)
            : this()
        {
            #region declarations
            List<string> drgFileLines = new List<string>();
            TextReader drgFileReader = new StreamReader(drgFileName);

            List<string> vspFileLines = new List<string>();
            TextReader vspFileReader = new StreamReader(vspFileName);

            #endregion

            #region read DRG file into memory
            try
            {
                string line;
                while ((line =  drgFileReader.ReadLine()) != null )
                {
                    drgFileLines.Add(line);
                }
            }
            catch { };
            #endregion

            #region Parse DRG file lines
            if (drgFileLines.Count > 0)
            {
                ParseDrgFileLines(drgFileLines.ToArray());
            }
            #endregion

            #region read VSP file into memory
            try
            {
                string line;
                while ((line = vspFileReader.ReadLine()) != null)
                {
                    vspFileLines.Add(line);
                }
            }
            catch { };
            #endregion

            #region Parse VSP file lines
            if (vspFileLines.Count > 0)
            {
                ParseVspFileLines(vspFileLines.ToArray());
            }
            #endregion
        }

        /// <summary>
        ///     Parse DRG file  from a project descriptor
        /// </summary>
        /// <param name="projectDescriptor"></param>
        public Parser( ProjectDescriptor projectDescriptor ) : this ()
        {
            if (projectDescriptor != null)
            {

                if (projectDescriptor.Results != null && projectDescriptor.Results.Equals(String.Empty) == false)
                {
                    string[] drgFileLines = projectDescriptor.Results.Split(new char[] { '\n', '\r' });
                    ParseDrgFileLines(drgFileLines);
                }

                if (projectDescriptor.Entities != null && projectDescriptor.Entities.Equals(String.Empty) == false)
                {
                    string[] vspFileLines = projectDescriptor.Entities.Split(new char[] { '\n', '\r' });
                    ParseVspFileLines(vspFileLines);
                }
            }
            
        }
        #endregion

        #region stuff
        //        Aproape e ieri,
        //        Departe e myine,
        //        Nu mai avem puteri,
        //        Noua ce ne ramyne ?
        #endregion

        #region file lines parsers
        /// <summary>
        ///     The parser for DRG file (core) engine
        /// </summary>
        /// <param name="drgFileLines">the content of the DRG file</param>
        private void ParseDrgFileLines (string[] drgFileLines)
        {
            
            if (drgFileLines  == null || drgFileLines.Length == 0)
            {
                throw new SolDevException("Results are not available");
            }

            Experiment lastExperiment = null;

            foreach(string drgLine in drgFileLines)
            {

                #region Experiments
                Experiment newExperiment = new Experiment(drgLine);
                if (newExperiment.IsValid)
                {
                    if (lastExperiment != null)
                    {
                        experiments.Add(lastExperiment);
                    }
                    lastExperiment = newExperiment;
                    continue;
                }
                #endregion

                #region Global variables
                GlobalVariable newGlobalVariable = new GlobalVariable(drgLine);
                if (newGlobalVariable.IsValid)
                {
                    if (lastExperiment == null)
                    {
                        lastExperiment = new Experiment();
                    }

                    lastExperiment.GlobalVariables.Add(newGlobalVariable);
                    continue;
                }
                #endregion

                #region Statistic Info
                StatisticInfo newStatisticInfo = new StatisticInfo(drgLine);
                if (newStatisticInfo.IsValid)
                {
                    if (lastExperiment == null)
                    {
                        lastExperiment = new Experiment();
                    }

                    lastExperiment.StatisticInfos.Add(newStatisticInfo);
                    continue;
                }
                #endregion

                #region Transaction
                Transaction newTransaction = new Transaction(drgLine);
                if (newTransaction.IsValid)
                {
                    if (lastExperiment == null)
                    {
                        lastExperiment = new Experiment();
                    }

                    lastExperiment.Transactions.Add(newTransaction);
                    continue;
                }
                #endregion
            }

            if (lastExperiment != null)
            {
                experiments.Add(lastExperiment);
            }
        }

        /// <summary>
        ///     The parser for VSP file (core) engine
        /// </summary>
        /// <param name="vspFileLines">the content of the VSP file divided out in lines</param>
        private void ParseVspFileLines(string[] vspFileLines)
        {

            if (vspFileLines == null || vspFileLines.Length == 0)
            {
                throw new SolDevException("Entities are not available");
            }


            foreach (string vspLine in vspFileLines)
            {
                
                Entity newEntity = new Entity(vspLine);
                if (newEntity.IsValid)
                {
                    entities.Add(newEntity);
                }
            }
        }
        #endregion

        #region Public properties
        /// <summary>
        ///     A list of detected experiments
        /// </summary>
        public List<Experiment> Experiments
        {
            get { return experiments; }
        }

        /// <summary>
        ///     A list of detected entities
        /// </summary>
        public List<Entity> Entities
        {
            get { return entities; }
        }
        #endregion
    }
}
